home *** CD-ROM | disk | FTP | other *** search
- /*
- * This program is copyright (C) 1992 by Vadim V. Vlasov, Moscow, Russia.
- *
- * The source is supplied as an example of interface to COMBI-disk (C)
- * device driver. You may change the source as You wish, however I'm not
- * responsible for the results of Your changes.
- *
- * The program is written for MS C 6.0 and may be compiled in TINY or
- * SMALL memory model.
- *
- * If You don't have ANSI.SYS installed or want to redirect output to a file
- * You may define NO_ANSI and recompile the program.
- *
- */
-
-
- #include <stdio.h>
- #include <string.h>
- #include <dos.h>
- #include "ioctl.h" /* definitions of structures and control codes */
-
- #ifndef NO_ANSI
- #define bold(string) "\x1b[1m"#string"\x1b[0m"
- #define red_bold(string) "\x1b[1;31m"#string"\x1b[0m"
- #define yellow_bold(string) "\x1b[1;33m"#string"\x1b[0m"
- #define cyan_bold(string) "\x1b[1;36m"#string"\x1b[0m"
- #else
- #define bold(string) #string
- #define red_bold(string) #string
- #define yellow_bold(string) #string
- #define cyan_bold(string) #string
- #endif
-
- main(int argc, char *argv[])
- {
- struct combi_status cmb_st;
- char choice, drive=2;
- union REGS r;
- void far * ptr;
- int i,j;
- char *chpt, optchar;
- char oldopt, opt;
-
- /*
- * Scan all drives and try to read IOCtl packet of length sizeof(cmb_st).
- * If successful then probably that drive is COMBI's RAM disk. To ensure
- * this we check that first 6 bytes of returned packet are "COMBI\0".
- */
-
- do {
- drive++;
- r.x.ax=0x4404;
- r.h.bl=drive;
- r.x.cx=sizeof(cmb_st);
- r.x.dx=(unsigned)&cmb_st;
- } while (((intdos(&r,&r)!=sizeof(cmb_st))||
- (r.x.cflag & 0x1)||
- strcmp(cmb_st.ID_name,"COMBI"))&&(drive < 16));
-
- if(drive >= 16) {
- printf(red_bold(Error: COMBI-disk not installed!(?)) "\n");
- exit(1);
- }
-
- printf("\t" yellow_bold(COMBI-disk version %1d.%02d installed as drive %c:) "\n",
- cmb_st.version >> 8, cmb_st.version & 0xff, drive+'A'-1);
-
- if(argc > 1) {
- optchar = '\0';
- oldopt = opt = cmb_st.COMBI_options;
-
- for(i=1; i < argc; i++) { /* Scan all command line arguments. */
-
- strlwr(argv[i]);
- if(isdigit(*argv[i]) || *argv[i]=='-' || *argv[i]=='+') {
-
- /* If an argument is a number then try to reallocate COMBI's
- * memory size.*/
-
- j = atoi(argv[i]);
- if(change_mem(drive, cmb_st.version, j))
- printf(red_bold(Can\'t reallocate memory!) "\a\n");
- else
- printf("Memory reallocated by %dK. ", j);
- } else {
- optchar = *argv[i];
- chpt = argv[i]+1;
- while(optchar) {
- switch(optchar) {
- case 'n':
- /* Option 'n' - ignore (or not ignore if 'n-')
- * 'sector not found error'. */
- if(*chpt == '-') {
- opt &= ~OPT_NO_SNF; /* Reset the option bit */
- chpt++;
- } else {
- opt |= OPT_NO_SNF; /* Set the option bit */
- if(*chpt == '+')
- chpt++;
- }
- optchar = *chpt++;
- break;
- case 'o':
- /* Option 'o' - turn cache on. */
- if(*chpt == '-') {
- opt |= OPT_OFF;
- chpt++;
- } else {
- opt &= ~OPT_OFF;
- if(*chpt == '+')
- chpt++;
- }
- optchar = *chpt++;
- break;
- case 'b':
- /* Option 'b' - turn background writing
- * (== write caching) on. */
- if(*chpt == '-') {
- opt &= ~OPT_WR_ON;
- chpt++;
- } else {
- opt |= OPT_WR_ON;
- if(*chpt == '+')
- chpt++;
- }
- optchar = *chpt++;
- break;
- case 'i':
- /* Option 'i' - write immediately
- * (or enable delayed writing if 'i-') in effect only if
- * write caching (background writing) is on. */
- if(*chpt == '-') {
- opt &= ~OPT_DW_OFF;
- chpt++;
- } else {
- opt |= OPT_DW_OFF;
- if(*chpt == '+')
- chpt++;
- }
- optchar = *chpt++;
- break;
- case 'z':
- /* Option 'z' - freeze cache - no new sectors are read into
- * cache after freezing and only that are in cache may be written
- * in background. */
- if(*chpt == '-') {
- opt &= ~OPT_FREEZE;
- chpt++;
- } else {
- opt |= OPT_FREEZE;
- if(*chpt == '+')
- chpt++;
- }
- optchar = *chpt++;
- break;
- case 'f':
- /* Option 'z' - fix memory setting - disables automatic reallocation
- * of XMS memory when it is requested by other programs. */
- if(*chpt == '-') {
- opt &= ~OPT_MEM;
- chpt++;
- } else {
- opt |= OPT_MEM;
- if(*chpt == '+')
- chpt++;
- }
- optchar = *chpt;
- break;
- case 'r':
- /* reset all counters */
- if(reset_counters(drive, cmb_st.version))
- printf(red_bold(Can\'t reset counters!) "\a\n");
- else
- printf("Counters reset. ");
- optchar = *chpt++;
- break;
- default:
- printf(red_bold(Invalid option: ) bold('%c') "\n", optchar);
- case '?':
- usage();
- }
- }
- }
- }
- if(oldopt != opt) {
- if(change_opt(drive, cmb_st.version, opt))
- printf(red_bold(Can\'t change options!) "\a\n");
- else
- printf("Options changed.");
- } else
- printf("Options unchanged.");
- printf("\n");
- }
-
- r.x.ax=0x4404; /* read again IOCtl packet */
- r.h.bl=drive;
- r.x.cx=sizeof(cmb_st);
- r.x.dx=(unsigned)&cmb_st;
- intdos(&r,&r);
-
- show_status(&cmb_st); /* Show status returned by COMBI. */
-
- }
-
- show_status(struct combi_status *cmb_st)
- {
- char opt;
-
- printf("\n\t" bold(Current status:) "\n");
-
- printf("buffer size: " cyan_bold(%5dK) "\n", cmb_st -> buff_size);
-
- printf("current size: " cyan_bold(%5dK) "\n", cmb_st -> curr_size);
-
- printf("total number of blocks: " cyan_bold(%4d) " (" cyan_bold(%d) " sectors each)\n",
- cmb_st -> n_blocks, cmb_st -> bl_sect);
-
- printf("current number of blocks: " cyan_bold(%4d) " (" cyan_bold(%d) " - RAM disk, " cyan_bold(%d) " - cache)\n",
- cmb_st -> n_curr, cmb_st -> n_bl_RD, cmb_st -> n_bl_Cache);
-
- opt = cmb_st -> COMBI_options;
- if(opt & OPT_WR_ON) { /* only if write caching is on */
- printf("dirty blocks: " cyan_bold(%d) ", errors: " cyan_bold(%d) "\n",
- cmb_st -> n_dirty, cmb_st -> n_errors);
- };
-
- printf("\n\t" bold(Options in order:) "\n");
-
- if(!(opt & OPT_OFF)) {
- printf("cache is " cyan_bold(on) " (%s),\n",
- (opt & OPT_FREEZE) ? "frozen" : "not frozen");
- printf("write caching is " cyan_bold(%s) ",\n",
- (opt & OPT_WR_ON) ? "on" : "off");
- if(opt & OPT_WR_ON) {
- printf("delayed write is " cyan_bold(%s) ",\n",
- (opt & OPT_DW_OFF) ? "off" : "on");
- };
- } else {
- printf("cache is " cyan_bold(off) ",\n");
- };
- printf("memory allocation is " cyan_bold(%s) ".\n",
- (opt & OPT_MEM) ? "fixed" : "not fixed");
-
- printf("\n\t" bold(Statistics:) "\n");
-
- printf("RAM disk reads: " cyan_bold(% 6u/%-6u) "\n",
- cmb_st -> read_RD_num, cmb_st -> read_RD_sect);
-
- printf("RAM disk writes:" cyan_bold(% 6u/%-6u) "\n",
- cmb_st -> write_RD_num, cmb_st -> write_RD_sect);
-
- if(!(opt & OPT_OFF)){
- printf("Hard disk reads - requested: " cyan_bold(% 6u/%-6u) ", passed to BIOS:" cyan_bold(% 6u/%-6u) "\n",
- cmb_st -> read_rq, cmb_st -> read_sect,
- cmb_st -> read_rq_a, cmb_st -> read_sect_a);
- printf("Hard disk writes - requested:" cyan_bold(% 6u/%-6u) ", passed to BIOS:" cyan_bold(% 6u/%-6u) "\n",
- cmb_st -> write_rq, cmb_st -> write_sect,
- cmb_st -> write_rq_a, cmb_st -> write_sect_a);
- }
- }
-
- change_mem(int drive, int ver, int memch)
- {
- unsigned char ctl[12];
- union REGS r;
- *(int *)&ctl = ver;
- if(memch > 0) {
- ctl[2] = CMD_EXPAND; /* command code for COMBI-disk - expand memory */
- *(int *)&ctl[3] = memch;/* the amount of Kbytes to change memory size */
- } else {
- ctl[2] = CMD_SHRINK; /* command code for COMBI-disk - shrink memory */
- *(int *)&ctl[3] = - memch;
- }
-
- r.x.ax=0x4405; /* DOS function: 'write IOCtl to block device' */
- r.h.bl=drive; /* device number */
- r.x.dx=(unsigned)&ctl; /* address of IOCtl packet */
- r.x.cx=5; /* IOCtl packet length */
- intdos(&r,&r);
- if(r.x.cflag & 01) /* test for error return code */
- return -1;
- else
- return 0;
- }
-
- change_opt(int drive, int ver, int opt)
- {
- unsigned char ctl[12];
- union REGS r;
- *(int *)&ctl = ver;
- ctl[2] = CMD_CH_OPT; /* command to COMBI-disk - change options */
- ctl[3] = opt; /* the byte with new options follows the command */
-
- r.x.ax=0x4405;
- r.h.bl=drive;
- r.x.dx=(unsigned)&ctl;
- r.x.cx=4;
- intdos(&r,&r);
- if(r.x.cflag & 01)
- return -1;
- else
- return 0;
- }
-
- reset_counters(int drive, int ver)
- {
- unsigned char ctl[12];
- union REGS r;
- *(int *)&ctl = ver;
- ctl[2] = CMD_RESET_C; /* command to COMBI-disk - reset counters */
- ctl[3] = 7; /* reset all three types of counters */
-
- r.x.ax=0x4405;
- r.h.bl=drive;
- r.x.dx=(unsigned)&ctl;
- r.x.cx=4;
- intdos(&r,&r);
- if(r.x.cflag & 01)
- return -1;
- else
- return 0;
- }
-
- usage()
- {
- printf("\t" yellow_bold(COMBI-disk (C) control program.) "\n"
- "Copyright (C) 1992 by Vadim V. Vlasov, Moscow, Russia.\n");
-
- printf("Usage: " bold(COMBI [[+|-]#] [<option>[+|-]]...) "\n"
- "where:\n"
- " " bold(# (number)) " - expand or shrink memory used by COMBI-disk,\n"
- " " bold(n) " - don't return 'sector not found' error,\n"
- " " bold(o) " - turn cache on ('" bold(o-) "' - turn off),\n"
- " " bold(b) " - turn write caching on ('" bold(b-) "' - off),\n"
- " " bold(i) " - start writing immediately ('" bold(i-) "' - delayed writing),\n"
- " " bold(f) " - fix memory settings ('" bold(f-) "' - release),\n"
- " " bold(z) " - freeze cache ('" bold(z-) "' - un-freese),\n"
- " " bold(r) " - reset all counters.\n");
- exit(1);
- }
-